home *** CD-ROM | disk | FTP | other *** search
/ Aminet 24 / Aminet 24 (1998)(GTI - Schatztruhe)[!][Apr 1998].iso / Aminet / comm / misc / CapiRexxVoiceM.lha / capi-usr.c < prev    next >
Encoding:
C/C++ Source or Header  |  1996-10-09  |  15.9 KB  |  626 lines

  1. /*
  2. **
  3. **    $Id: capi-usr.c,v 1.876 1996/08/13 03:16:27 chris Exp $
  4. **
  5. **    $Filename: arch/amigados/capi-usr.c $
  6. **    $Author: chris $
  7. **    $Portability: Amiga $
  8. **
  9. **    CAPI-User interface to the Amiga capi20.device. This interface makes the
  10. **    application's call to the CAPI driver independant from the operating
  11. **    system running the CAPI. For every supported OS there is a different
  12. **    CAPI-User.c interface.
  13. **
  14. **    No warranty. Use at your own risk.
  15. **
  16. **    COPYRIGHT (C) 1993-1996 BY RELOG AG, ZUERICH. ALL RIGHTS RESERVED.
  17. **    NO PART OF THIS SOFTWARE MAY BE COPIED, REPRODUCED, OR TRANSMITTED
  18. **    IN ANY FORM OR BY ANY MEANS,  WITHOUT THE PRIOR WRITTEN PERMISSION
  19. **    OF RELOG AG.
  20. **
  21. */
  22.  
  23. #include "os.h"
  24. #include "capi-usr.h"
  25. #include "capibase.h"
  26.  
  27. #include <string.h>
  28.  
  29. #include <exec/types.h>
  30. #include <exec/nodes.h>
  31. #include <exec/lists.h>
  32. #include <exec/memory.h>
  33. #include <exec/io.h>
  34. #include <exec/semaphores.h>
  35. #include <proto/exec.h>
  36.  
  37. #define ObtainSemaphore(x)
  38. #define ReleaseSemaphore(x)
  39.  
  40.  
  41. /*
  42. **    Folgende Struktur wird für jedes CAPI_REGISTER erzeugt:
  43. */
  44. struct UserApp
  45. {
  46.     struct Node                Node;        /* Verkettung */
  47.     struct SignalSemaphore    Lock;        /* Schützt IO */
  48.     struct IOExtCAPI        IO;
  49. };
  50.  
  51.  
  52. /*
  53. **    Statischer IO-Request für Applikationsunabhängige Kommandos
  54. */
  55. static struct UserApp        g_app;
  56. static BOOL                    initialized;
  57.  
  58.  
  59. /*
  60. **    Liste für Mapping ApplID->UserApp
  61. */
  62. static struct List            applist;
  63.  
  64.  
  65. /*
  66. **    First-Time-Initialisierung
  67. */
  68. static VOID FirstTimeInit( VOID )
  69. {
  70.     if (!initialized)
  71.     {
  72.         NewList( &applist );
  73.         InitSemaphore( &g_app.Lock );
  74.         initialized = TRUE;
  75.     }
  76. }
  77.  
  78.  
  79. static VOID AddUserApp( struct UserApp *app )
  80. {
  81.     Forbid();
  82.     AddTail( (struct List *)&applist, &app->Node );
  83.     Permit();
  84. }
  85.  
  86.  
  87. static VOID RemoveUserApp( struct UserApp *app )
  88. {
  89.     Forbid();
  90.     Remove( &app->Node );
  91.     Permit();
  92. }
  93.  
  94.  
  95. static struct UserApp *FindUserApp( unsigned short applID )
  96. {
  97.     struct UserApp *app;
  98.  
  99.     if (applID == 0)    /* 0 ist immer ungültig */
  100.         return NULL;
  101.  
  102.     Forbid();
  103.     DOLIST( (IC_LIST *)&applist, app )
  104.     {
  105.         if ((unsigned short)app->IO.IOCAPI.io_Unit == applID)
  106.         {
  107.             Permit();
  108.             return app;
  109.         }
  110.     }
  111.     Permit();
  112.  
  113.     return NULL;
  114. }
  115.  
  116.  
  117.  
  118. /****** U_CAPI_REGISTER *****************************************************
  119. *
  120. *   NAME
  121. *       U_CAPI_REGISTER -- Register an application with the CAPI
  122. *
  123. *   SYNOPSIS
  124. *       result = U_CAPI_REGISTER( maxLogicalConnection, maxBDataBlocks,
  125. *                                 maxBDataLen, pApplId );
  126. *
  127. *       unsigned U_CAPI_REGISTER( unsigned, unsigned,
  128. *                                 unsigned, unsigned short * );
  129. *
  130. *   FUNCTION
  131. *       This is the operation the application uses to report its presence
  132. *       to the CAPI. By passing the four first parameters, the application
  133. *       describes its needs.
  134. *
  135. *   INPUTS
  136. *       maxLogicalConnection - Maximum number of logical connections
  137. *       maxBDataBlocks       - Number of data blocks available simultaneously
  138. *       maxBDataLen          - Maximum size of a data block
  139. *       pApplId              - Pointer to the location where CAPI should place
  140. *                              the ID of the newly registered application.
  141. *                              A valid ID will never be zero.
  142. *
  143. *   RESULT
  144. *       0 if successful, or parameter info class 0x10xx
  145. *
  146. *   SEE ALSO
  147. *       U_CAPI_RELEASE()
  148. *
  149. ****************************************************************************/
  150.  
  151. unsigned
  152. U_CAPI_REGISTER( unsigned maxLogicalConnection, unsigned maxBDataBlocks, unsigned maxBDataLen,
  153.                     unsigned short *pApplID )
  154. {
  155.     struct UserApp    *app;
  156.     unsigned        result;
  157.  
  158.     FirstTimeInit();
  159.  
  160.  
  161.     /*
  162.     **    Neuen IO-Request für diese Applikation erzeugen
  163.     */
  164.     if ((app = AllocVec( sizeof( *app ), MEMF_CLEAR )) != NULL)
  165.     {
  166.         InitSemaphore( &app->Lock );
  167.  
  168.         app->IO.Level3Cnt    = maxLogicalConnection;
  169.         app->IO.DataBlkCnt    = maxBDataBlocks;
  170.         app->IO.DataBlkLen    = maxBDataLen;
  171.         app->IO.CAPIResult    = CAPI_10_CAPI_NOT_INSTALLED;
  172.  
  173. /*        kprintf( "U_CAPI_REGISTER(): Level3Cnt=%ld, DataBlkCnt=%ld, DataBlkLen=%ld\n",
  174.             (long)app->IO.Level3Cnt, (long)app->IO.DataBlkCnt, (long)app->IO.DataBlkLen ); */
  175.  
  176.         if (OpenDevice( CAPINAME, 0, (struct IORequest *)&app->IO, NULL) == 0)
  177.         {
  178.             AddUserApp( app );
  179.             *pApplID = (unsigned short)app->IO.IOCAPI.io_Unit;
  180.             result = CAPI_00_REQUEST_ACCEPTED;
  181.         }
  182.         else result = app->IO.CAPIResult;
  183.     }
  184.     else result = CAPI_10_OS_RESOURCE_ERROR;
  185.  
  186.     if (result != CAPI_00_REQUEST_ACCEPTED)
  187.     {
  188.         U_CAPI_RELEASE( (unsigned short)app );
  189.         *pApplID = 0;
  190.     }
  191.  
  192.     return result;
  193. }
  194.  
  195.  
  196. /****** U_CAPI_RELEASE ******************************************************
  197. *
  198. *   NAME
  199. *       U_CAPI_RELEASE -- Terminate access to the CAPI
  200. *
  201. *   SYNOPSIS
  202. *       result = U_CAPI_RELEASE( applId );
  203. *
  204. *       unsigned U_CAPI_RELEASE( unsigned short );
  205. *
  206. *   FUNCTION
  207. *       The application uses this operation to log off from CAPI.
  208. *       CAPI will release all resources that have been allocated.
  209. *
  210. *   INPUTS
  211. *       applId - Application ID as received from CAPI_REGISTER(),
  212. *                or zero for no action.
  213. *
  214. *   RESULT
  215. *       0 if successful, or parameter info class 0x11xx
  216. *
  217. *   SEE ALSO
  218. *       U_CAPI_REGISTER()
  219. *
  220. ****************************************************************************/
  221.  
  222. unsigned
  223. U_CAPI_RELEASE( unsigned short applID )
  224. {
  225.     struct UserApp *app;
  226.  
  227.     FirstTimeInit();
  228.  
  229.     if ((app = FindUserApp( applID )) != NULL)
  230.     {
  231.         RemoveUserApp( app );
  232.  
  233.         if ((ULONG)app->IO.IOCAPI.io_Device > 0)
  234.             CloseDevice( (struct IORequest *)&app->IO );
  235.  
  236.         FreeVec( app );
  237. /*        app = NULL; */
  238.  
  239.         return CAPI_00_REQUEST_ACCEPTED;
  240.     }
  241.  
  242.     return CAPI_11_ILLEGAL_APPLID;
  243. }
  244.  
  245.  
  246. /****** U_CAPI_PUT_MESSAGE **************************************************
  247. *
  248. *   NAME
  249. *       U_CAPI_PUT_MESSAGE -- Send a message from the application to the CAPI
  250. *
  251. *   SYNOPSIS
  252. *       result = U_CAPI_PUT_MESSAGE( applId, pCAPIMessage );
  253. *
  254. *       unsigned U_CAPI_PUT_MESSAGE( unsigned short, CAPI_MESSAGE * );
  255. *
  256. *   FUNCTION
  257. *       With this operation the application transfers a message to the CAPI.
  258. *       Under OS/2, the message memory area must not cross a 64 kByte
  259. *       boundary in the flat address space because the DLL may convert the
  260. *       passed flat pointer to a 16:16 bit segmented pointer.
  261. *
  262. *   INPUTS
  263. *       applId       - Application ID as received from U_CAPI_REGISTER()
  264. *       pCAPIMessage - Pointer to the message
  265. *
  266. *   RESULT
  267. *       0 if successful, or parameter info class 0x11xx
  268. *
  269. *   SEE ALSO
  270. *       U_CAPI_GET_MESSAGE()
  271. *
  272. ****************************************************************************/
  273.  
  274. unsigned
  275. U_CAPI_PUT_MESSAGE( unsigned short applID, CAPI_MESSAGE *pMessage )
  276. {
  277.     struct UserApp *app;
  278.     unsigned result = CAPI_10_CAPI_NOT_INSTALLED;
  279.  
  280.     if ((app = FindUserApp( applID )) != NULL)
  281.     {
  282.         ObtainSemaphore( &app->Lock );
  283.         app->IO.IOCAPI.io_Command = CAPIIOCMD_PUT_MESSAGE;
  284.         app->IO.IOCAPI.io_Data = pMessage;
  285.         (void)DoIO( (struct IORequest *)&app->IO );
  286.         result = app->IO.CAPIResult;
  287.         ReleaseSemaphore( &app->Lock );
  288.     }
  289.  
  290.     return result;
  291. }
  292.  
  293.  
  294. /****** U_CAPI_GET_MESSAGE ***************************************************
  295. *
  296. *   NAME
  297. *       U_CAPI_GET_MESSAGE -- Get a message from the CAPI
  298. *
  299. *   SYNOPSIS
  300. *       result = U_CAPI_GET_MESSAGE( applId, ppCAPIMessage );
  301. *
  302. *       unsigned U_CAPI_GET_MESSAGE( unsigned short, CAPI_MESSAGE ** );
  303. *
  304. *   FUNCTION
  305. *       With this operation the application retrieves a message from the CAPI.
  306. *       The application can only retrieve those messages intended for the
  307. *       stipulated application identification number. If there is no message
  308. *       waiting for retrieval, the function returns immediately with an
  309. *       error code.
  310. *
  311. *   INPUTS
  312. *       applId        - Application ID as received from U_CAPI_REGISTER()
  313. *       ppCAPIMessage - Pointer to the memory location where CAPI should
  314. *                       place a pointer to the data of the retrieved message
  315. *
  316. *   RESULT
  317. *       0 if successful, or parameter info class 0x11xx
  318. *
  319. *   SEE ALSO
  320. *       U_CAPI_PUT_MESSAGE()
  321. *
  322. ****************************************************************************/
  323.  
  324. unsigned
  325. U_CAPI_GET_MESSAGE( unsigned short applID, CAPI_MESSAGE **ppMessage )
  326. {
  327.     struct UserApp *app;
  328.     unsigned result = CAPI_10_CAPI_NOT_INSTALLED;
  329.  
  330.     if ((app = FindUserApp( applID )) != NULL)
  331.     {
  332.         ObtainSemaphore( &app->Lock );
  333.         app->IO.IOCAPI.io_Command = CAPIIOCMD_GET_MESSAGE;
  334.         (void)DoIO( (struct IORequest *)&app->IO );
  335.  
  336.         if ((result = app->IO.CAPIResult) == 0)
  337.             *ppMessage = (CAPI_MESSAGE *)app->IO.IOCAPI.io_Actual;
  338.         else
  339.             *ppMessage = NULL;
  340.  
  341.         ReleaseSemaphore( &app->Lock );
  342.     }
  343.  
  344.     return result;
  345. }
  346.  
  347.  
  348. /****** U_CAPI_SET_SIGNAL ***************************************************
  349. *
  350. *   NAME
  351. *       U_CAPI_SET_SIGNAL -- Install a signalling mechanism
  352. *
  353. *   SYNOPSIS
  354. *       success = U_CAPI_SET_SIGNAL( applId, callback, para );
  355. *
  356. *       unsigned short U_CAPI_SET_SIGNAL( unsigned short, unsigned long,
  357. *                                         unsigned long );
  358. *
  359. *   FUNCTION
  360. *       This operation is used by the application to install a mechanism
  361. *       which signals the application the availability of a message.
  362. *
  363. *       In that case each time CAPI places a message in the application's
  364. *       message queue, the specified callback function is called.
  365. *
  366. *       By issuing this function call with a callback value of 0 the
  367. *       signalling mechanism is deactivated.
  368. *
  369. *       The called function must have the following format:
  370. *       void callback( unsigned short applID, unsigned long para );
  371. *
  372. *   INPUTS
  373. *       applId   - ID of Application posting the request
  374. *       callback - Pointer to the function to be called
  375. *       para     - Parameter passed to callback function (application's use)
  376. *
  377. *   RESULT
  378. *       success - 0 if OK, or parameter info class 11 upon failure.
  379. *
  380. *   SEE ALSO
  381. *
  382. ****************************************************************************/
  383.  
  384. unsigned short
  385. U_CAPI_SET_SIGNAL( unsigned short applID, unsigned long callback, unsigned long para )
  386. {
  387.     struct UserApp *app;
  388.  
  389.     if ((app = FindUserApp( applID )) != NULL)
  390.     {
  391.         ObtainSemaphore( &app->Lock );
  392.         app->IO.IOCAPI.io_Command = CAPIIOCMD_SET_SIGNAL;
  393.         app->IO.IOCAPI.io_Data = (APTR)callback;
  394.         app->IO.IOCAPI.io_Offset = para;
  395.         (void)DoIO( (struct IORequest *)&app->IO );
  396.         ReleaseSemaphore( &app->Lock );
  397.  
  398.         return CAPI_00_REQUEST_ACCEPTED;
  399.     }
  400.  
  401.     return CAPI_11_ILLEGAL_APPLID;
  402. }
  403.  
  404.  
  405. /*
  406. **    Capi-IO mit statischem IO-Request durchführen. Die Semaphore g_app.Lock
  407. **    muss vor dem Aufruf schon gelockt sein, und wird hier wieder freigegeben!
  408. */
  409. static unsigned DoCAPIIO( UWORD command )
  410. {
  411.     unsigned result;
  412.  
  413.     g_app.IO.IOCAPI.io_Command = command;
  414.  
  415.     /*
  416.     **    Wir öffnen das device mit flags == 1, was bedeutet, dass kein CAPI_REGISTER
  417.     **    gemacht wird.
  418.     */
  419.     if (OpenDevice( CAPINAME, 0, (struct IORequest *)&g_app.IO, 1) == 0)
  420.     {
  421.         (void)DoIO( (struct IORequest *)&g_app.IO );
  422.         result = g_app.IO.CAPIResult;
  423.         CloseDevice( (struct IORequest *)&g_app.IO );
  424.     }
  425.     else result = CAPI_10_CAPI_NOT_INSTALLED;
  426.  
  427.     ReleaseSemaphore( &g_app.Lock );
  428.     return result;
  429. }
  430.  
  431.  
  432. /****** U_CAPI_GET_MANUFACTURER *********************************************
  433. *
  434. *   NAME
  435. *       U_CAPI_GET_MANUFACTURER -- Get manufacturer ID of the CAPI driver
  436. *
  437. *   SYNOPSIS
  438. *       U_CAPI_GET_MANUFACTURER( SzBuffer );
  439. *
  440. *       void U_CAPI_GET_MANUFACTURER( char * );
  441. *
  442. *   FUNCTION
  443. *       With this operatrion the application determines the manufacturer
  444. *       identification of the installed CAPI driver. SzBuffer on call is
  445. *       a pointer to a buffer of 64 bytes. CAPI copies the identification
  446. *       string, coded as a zero-terminated ASCII string, to this buffer.
  447. *
  448. *   INPUTS
  449. *       SzBuffer - Pointer to a buffer of 64 bytes
  450. *
  451. *   RESULT
  452. *       none
  453. *
  454. *   SEE ALSO
  455. *       U_CAPI_GET_VERSION(), U_CAPI_GET_SERIAL_NUMBER()
  456. *
  457. ****************************************************************************/
  458.  
  459. void
  460. U_CAPI_GET_MANUFACTURER( char *SzBuffer )
  461. {
  462.     FirstTimeInit();
  463.  
  464.     ObtainSemaphore( &g_app.Lock );
  465.     g_app.IO.IOCAPI.io_Data = SzBuffer;
  466.     (void)DoCAPIIO( CAPIIOCMD_GET_MANUFACTURER );
  467. }
  468.  
  469.  
  470. /****** U_CAPI_GET_VERSION **************************************************
  471. *
  472. *   NAME
  473. *       U_CAPI_GET_VERSION -- Get CAPI version numbers
  474. *
  475. *   SYNOPSIS
  476. *       result = U_CAPI_GET_VERSION( pVersionNumbers )
  477. *
  478. *       void U_CAPI_GET_VERSION( unsigned long * );
  479. *
  480. *   FUNCTION
  481. *       With this function the appplication determines the version of the
  482. *       CAPI as well as an internal version number.
  483. *
  484. *   INPUTS
  485. *       pVersionNumbers - Pointer to an array of four U32s receiving
  486. *                         the following four version numbers:
  487. *
  488. *                         1st: CAPI major version number (currently 2)
  489. *                         2nd: CAPI minor version number (currently 0)
  490. *                         3rd: Manufacturer specific major version number
  491. *                         4th: Manufacturer specific minor version number
  492. *
  493. *   RESULT
  494. *       none
  495. *
  496. *   SEE ALSO
  497. *       U_CAPI_GET_MANUFACTURER(), U_CAPI_GET_SERIAL_NUMBER()
  498. *
  499. ****************************************************************************/
  500.  
  501. void
  502. U_CAPI_GET_VERSION( unsigned long *pVersionNumbers )
  503. {
  504.     FirstTimeInit();
  505.  
  506.     ObtainSemaphore( &g_app.Lock );
  507.     g_app.IO.IOCAPI.io_Data = pVersionNumbers;
  508.     (void)DoCAPIIO( CAPIIOCMD_GET_VERSION );
  509. }
  510.  
  511.  
  512. /****** U_CAPI_GET_SERIAL_NUMBER ********************************************
  513. *
  514. *   NAME
  515. *       U_CAPI_GET_SERIAL_NUMBER -- Get the serial number of the CAPI
  516. *
  517. *   SYNOPSIS
  518. *       result = U_CAPI_GET_SERIAL_NUMBER( SzBuffer );
  519. *
  520. *       void U_CAPI_GET_SERIAL_NUMBER( char * );
  521. *
  522. *   FUNCTION
  523. *       With this operation the application determines the (optional) serial
  524. *       number of the CAPI. SzBuffer on call is a pointer to a buffer of 8
  525. *       bytes. CAPI copies the serial number string to this buffer. The serial
  526. *       number, coded as a zero terminated ASCII string, represents a seven
  527. *       digit number after the function has returned.
  528. *
  529. *   INPUTS
  530. *       SzBuffer - Pointer to a buffer of 8 bytes
  531. *
  532. *   RESULT
  533. *       none
  534. *
  535. *   SEE ALSO
  536. *       U_CAPI_GET_VERSION(), U_CAPI_GET_MANUFACTURER()
  537. *
  538. ****************************************************************************/
  539.  
  540. void
  541. U_CAPI_GET_SERIAL_NUMBER( char *SzBuffer )
  542. {
  543.     FirstTimeInit();
  544.  
  545.     ObtainSemaphore( &g_app.Lock );
  546.     g_app.IO.IOCAPI.io_Data = SzBuffer;
  547.     (void)DoCAPIIO( CAPIIOCMD_GET_SERIAL_NUMBER );
  548. }
  549.  
  550.  
  551. /****** U_CAPI_GET_PROFILE **************************************************
  552. *
  553. *   NAME
  554. *       U_CAPI_GET_PROFILE -- Get the profile of a controller
  555. *
  556. *   SYNOPSIS
  557. *       result = U_CAPI_GET_PROFILE( SzBuffer, CtrlNr );
  558. *
  559. *       unsigned U_CAPI_GET_PROFILE( CAPI_PROFILE *, unsigned short );
  560. *
  561. *   FUNCTION
  562. *       The application uses this function to get the capabilities from CAPI.
  563. *       SzBuffer on call is a pointer to a buffer of 64 bytes. In this buffer
  564. *       CAPI copies information about implemented features, number of
  565. *       controllers and supported protocols. CtrlNr contains the controller
  566. *       number (bit 0..6) for which this information is requested.
  567. *
  568. *   INPUTS
  569. *       SzBuffer - Pointer to a buffer receiving the CAPI_PROFILE structure.
  570. *       CtrlNr   - Number of controller. If 0, only the number of installed
  571. *                  controllers is given to the application.
  572. *
  573. *   RESULT
  574. *       0 if successful, or parameter info class 0x11xx
  575. *
  576. *   SEE ALSO
  577. *
  578. ****************************************************************************/
  579.  
  580. unsigned
  581. U_CAPI_GET_PROFILE( CAPI_PROFILE *SzBuffer, unsigned short CtrlNr )
  582. {
  583.     FirstTimeInit();
  584.  
  585.     ObtainSemaphore( &g_app.Lock );
  586.     g_app.IO.IOCAPI.io_Data = SzBuffer;
  587.     g_app.IO.IOCAPI.io_Offset = CtrlNr;
  588.     return DoCAPIIO( CAPIIOCMD_GET_PROFILE );
  589. }
  590.  
  591.  
  592. /****** U_CAPI_INSTALLED ****************************************************
  593. *
  594. *   NAME
  595. *       U_CAPI_INSTALLED -- Find out if a CAPI driver is installed
  596. *
  597. *   SYNOPSIS
  598. *       result = U_CAPI_INSTALLED();
  599. *
  600. *       unsigned U_CAPI_INSTALLED( void );
  601. *
  602. *   FUNCTION
  603. *       The application can use this function to find out if the CAPI
  604. *       driver is installed.
  605. *
  606. *   INPUTS
  607. *       none
  608. *
  609. *   RESULT
  610. *       0 if capi is installed, non-zero otherwise.
  611. *
  612. *   SEE ALSO
  613. *
  614. ****************************************************************************/
  615.  
  616. unsigned
  617. U_CAPI_INSTALLED( void )
  618. {
  619.     CAPI_PROFILE profile;
  620.     return U_CAPI_GET_PROFILE( &profile, 0 );
  621. }
  622.  
  623.  
  624.  
  625. /* End of CAPI-Usr.c */
  626.